#include "logic.h"

ILogic* getLogic()
{
	ILogic* p_logic = new Logic();
	return p_logic;
}

Logic::Logic()
{
	QLibrary libBridge("Bridge.dll");
	if (!libBridge.load())
		qDebug() << libBridge.errorString();
	if (libBridge.load())
		qDebug() << "bridge library loaded";

	typedef IBridge*(*getBridgeFunction)(void);
	getBridgeFunction createBridge = (getBridgeFunction)libBridge.resolve("getBridge");
	if (createBridge) 
	{
		_bridge = createBridge();
	} else {
		qDebug() << "Could not get Bridge from the loaded library";
	}
}

Logic::~Logic()
{
	Stop();
}

void Logic::Start()
{
	_bridge->startServer();
}

QStringList Logic::DeviceParcer()
{
	QStringList notParsedDevice = _bridge->getDevices().split(' ');
	for(int i =0; i < 4; i++)
		notParsedDevice.removeFirst(); //removing strings "List of devices attached"
	QStringList temp = notParsedDevice.last().split('\t');	
	QStringList tmp;
	foreach (QString strg, temp)
	{
		tmp << strg.split('\n');
	}	
	for(int i =0; i<tmp.count() ;i++)
	{
		tmp[i] = tmp[i].simplified();
		if(tmp[i].isEmpty())
		{
			tmp.removeAt(i);
			i--;
		}
	}
	QString props;
	QStringList properties;
	for(int j =0; j < tmp.count();j+=2)
	{
		props = _bridge->getDevicesProps(tmp[j]);		
		properties << props.split('\n');		
	}
	for(int i = 0; i < properties.count(); ++i )
	{
		properties[i] = properties[i].simplified();
		if(!(properties.at(i).contains("[ro.product.model]") || properties.at(i).contains("[ro.product.manufacturer]")))
		{

			properties.removeAt(i);
			i--;
		}
	}
	for(int i =0;i<properties.count();i++)
	{
		if(properties[i].contains("[ro.product.model]: ["))
			properties[i].remove("[ro.product.model]: [");
		if(properties[i].contains("[ro.product.manufacturer]: ["))
			properties[i].remove("[ro.product.manufacturer]: [");
		if(properties[i].contains("]"))
			properties[i].remove("]");		
	}
	qDebug()<<"prop 1"<<properties;
	for(int i =0;i<properties.count();i+=2)
	{
		tmp[i+1] = properties[i] +" "+properties[i+1];
	}
	qDebug()<<"temp device parser"<<tmp;
	return tmp;
}

QList<Devices> Logic::getDevices()
{
	QList<Devices> devicesList;
	QStringList unParsedDevices = DeviceParcer();
	int size = unParsedDevices.size();
	qDebug()<<unParsedDevices;
	Devices tmp;
	for(int i=0;i<size;i++)
	{
		tmp.name = unParsedDevices.at(i);
		i++;
		tmp.model = unParsedDevices.at(i);
		devicesList.append(tmp); 
	}
	return devicesList;

}

void Logic::selectedDevice(QString currentDevice)
{
	_bridge->setSelectedDevice(currentDevice);
}

bool Logic::getScreenshot(QString str)
{
	bool b = _bridge->getScreenshot(str);
	return b;
}
		
QList<FileSystem> Logic::fileSystemParcer(QString path)
{
	QStringList splitted = _bridge->getFileSystem(path).split('\n');
	QList<FileSystem> fileSystemList;
	FileSystem tmpFileSystem;

	for (int i=0;i<splitted.count();i++)
	{
		splitted[i].replace("\r\r","");
		if (splitted[i].isEmpty() || splitted[i].at(0) == 'l') 
		{
			splitted.removeAt(i);
			i--;
		}
	}

/*
	for(int i=0;i<splitted.count();i++)
		qDebug() << i << ":" <<splitted[i];*/
	
	fileSystemList.clear();
	QRegExp re("[0-9]{4}\\-[0-9]{2}\\-[0-9]{2} [0-9]{2}:[0-9]{2} ");
	int index;

	for(int i=0;i<splitted.count();i++)
	{
		//PARSE
		index=splitted[i].indexOf(re,0);
		if (index!=-1)
		{
			tmpFileSystem.Time = splitted[i].mid(index,16); 
			splitted[i].remove(index,17); //remove time substring

			int copy_length=splitted[i].length()-index;
			tmpFileSystem.Name = splitted[i].right(copy_length);
			splitted[i].remove(index-1,copy_length+1);//remove file name substring

			if (splitted[i].at(0) == 'd') tmpFileSystem.directory=true;
				else tmpFileSystem.directory=false;

			tmpFileSystem.Permissions = splitted[i].mid(1,9);
			splitted[i].remove(0,11); //remove permissions substring

			if (tmpFileSystem.directory)
			{
				tmpFileSystem.Size=-1;
			}
			else
			{
				splitted[i]=splitted[i].simplified();
				QStringList sizeString=splitted[i].split(" ");
				tmpFileSystem.Size=sizeString.last().toInt();
			}
			fileSystemList.append(tmpFileSystem);			
		}	
	}
	splitted.clear();

	return fileSystemList;
}


QList<FileSystem> Logic::getFileSystem(QString s)
{
	QList<FileSystem> parsedFileSystem = fileSystemParcer(s);
	return parsedFileSystem;
}

bool Logic::newFolder(QString name, QString path)
{	
	return _bridge->newFolder(name,path);
}

bool Logic::Delete(QString filePath, QString fileName)
{
	return _bridge->Delete(filePath,fileName);
}
//path to .apk file, and prefered location to install(local memory or sdcard :(false/true))
bool Logic::Install(QString path,bool installTo)
{
	QString arg = " install ";
	if (installTo) arg += "-s ";
	QString str = arg + "\""+ path +"\"";
	bool res = _bridge->Install(str);
	return res;  
}


bool Logic::Paste(QString destinationPath,QStringList list,bool isOnCopy)
{
	return _bridge->moveFiles(list,destinationPath,isOnCopy);
}


void Logic::Stop()
{
	_bridge->killServer();
}

bool Logic::makeBackup(QString path,bool apk,bool shared)
{	
	QString str,apkStr,sharedStr;
	if(apk)
		apkStr = " -apk";
	else
		apkStr = " -noapk";

	if(shared)
		sharedStr = " -shared ";
	else
		sharedStr = " -noshared ";
	str = apkStr;
	str += sharedStr;
	str += "-all -f \"";
	str += path;
	str += "\"";

	qDebug() << str;
	return _bridge->makeBackup(str);
}

bool Logic::Restore(QString path)
{
	return _bridge->restoreBackup(path);
}

bool Logic::Push(QString filePath,QString devicePath)
{
	bool res=_bridge->pushToDevice(filePath,devicePath);
	return res;
}

bool Logic::Pull(QString filePathOnDevice,QString pullPath)
{
	bool res=_bridge->pullFromDevice(filePathOnDevice,pullPath);
	return res;
}




